﻿using AutoMapper;
using ClosedXML.Excel;
using ERP.Team.HumanResources;
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Linq.Dynamic.Core;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
using Volo.Abp.Application.Dtos;
using Volo.Abp.Application.Services;
using Volo.Abp.Domain.Repositories;

namespace ERP.ERPSystem.HumanResources
{
    /// <summary>
    /// 入职申请应用服务实现类
    /// </summary>
    public class OnboardingServices : ApplicationService, IOnboardingServices
    {
        /// <summary>
        /// 入职审核仓储
        /// </summary>
        private readonly IRepository<OnboardingReview> _onboardingreview;
        /// <summary>
        /// 映射器
        /// </summary>
        private readonly IMapper _mapper;
        /// <summary>
        /// 构造函数，通过依赖注入获取仓储和映射器的实例
        /// </summary>
        /// <param name="onboardingreview">入职审核仓储</param>
        /// <param name="mapper">AutoMapper实例</param>
        public OnboardingServices(IRepository<OnboardingReview> onboardingreview, IMapper mapper)
        {
            _onboardingreview = onboardingreview;
            _mapper = mapper;
        }

        /// <summary>
        /// 分页查询入职申请数据 (已优化性能)
        /// </summary>
        /// <param name="PersonName">(筛选条件) 申请人姓名</param>
        /// <param name="InterviewPeople">(筛选条件) 面试官姓名</param>
        /// <param name="page">页码，从1开始</param>
        /// <param name="pageSize">每页数量</param>
        /// <returns>分页的入职审核实体列表</returns>
        public async Task<PagedResultDto<OnboardingReview>> QueryPaged(
            string? PersonName,
            string? InterviewPeople,
            int page = 1,
            int pageSize = 10)
        {
            // 1. 获取 IQueryable 对象，以便在数据库层面执行筛选和分页
            var queryable = await _onboardingreview.GetQueryableAsync();

            // 2. 应用筛选条件
            var query = queryable
                .WhereIf(!string.IsNullOrWhiteSpace(PersonName), o => o.PersonName.Contains(PersonName))
                .WhereIf(!string.IsNullOrWhiteSpace(InterviewPeople), o => o.InterviewPeople.Contains(InterviewPeople));

            // 3. 获取筛选后的总记录数
            var totalCount = await AsyncExecuter.CountAsync(query);

            // 4. 应用排序和分页
            var pagedItems = await AsyncExecuter.ToListAsync(
                query.OrderByDescending(x => x.InterviewTime) // 按面试时间倒序排序
                     .Skip((page - 1) * pageSize)
                     .Take(pageSize)
            );

            // 5. 返回标准分页结果对象
            return new PagedResultDto<OnboardingReview>
            {
                TotalCount = totalCount,
                Items = pagedItems
            };
        }

        /// <summary>
        /// 根据当前筛选条件导出数据到Excel文件 (已优化性能)
        /// </summary>
        /// <param name="PersonName">(筛选条件) 申请人姓名</param>
        /// <param name="InterviewPeople">(筛选条件) 面试官姓名</param>
        /// <returns>Excel文件的字节数组</returns>
        public async Task<byte[]> ExportToExcel(string? PersonName, string? InterviewPeople)
        {
            // 1. 使用与分页查询相同的逻辑在数据库层面筛选数据
            var queryable = await _onboardingreview.GetQueryableAsync();
            var query = queryable
                .WhereIf(!string.IsNullOrWhiteSpace(PersonName), o => o.PersonName.Contains(PersonName))
                .WhereIf(!string.IsNullOrWhiteSpace(InterviewPeople), o => o.InterviewPeople.Contains(InterviewPeople));
            
            var itemsToExport = await AsyncExecuter.ToListAsync(query.OrderByDescending(x => x.InterviewTime));

            // 2. 创建Excel工作簿和工作表
            using var workbook = new XLWorkbook();
            var worksheet = workbook.Worksheets.Add("入职申请数据");

            // 3. 设置表头
            worksheet.Cell(1, 1).Value = "人员名称";
            worksheet.Cell(1, 2).Value = "联系电话";
            worksheet.Cell(1, 3).Value = "用户性别";
            worksheet.Cell(1, 4).Value = "定级";
            worksheet.Cell(1, 5).Value = "面试反馈";
            worksheet.Cell(1, 6).Value = "面试结果";
            worksheet.Cell(1, 7).Value = "面试次数";
            worksheet.Cell(1, 8).Value = "面试时间";
            worksheet.Cell(1, 9).Value = "面试官";
            
            // 4. 填充数据行
            for (int i = 0; i < itemsToExport.Count; i++)
            {
                var item = itemsToExport[i];
                var row = i + 2;
                worksheet.Cell(row, 1).Value = item.PersonName;
                worksheet.Cell(row, 2).Value = item.Phone;
                worksheet.Cell(row, 3).Value = item.Sex == 1 ? "男" : (item.Sex == 2 ? "女" : "未知");
                worksheet.Cell(row, 4).Value = item.GradingMatch;
                worksheet.Cell(row, 5).Value = item.InterviewFeedback;
                worksheet.Cell(row, 6).Value = item.InterviewResult;
                worksheet.Cell(row, 7).Value = item.InterviewNumber;
                worksheet.Cell(row, 8).Value = item.InterviewTime.ToString("yyyy-MM-dd");
                worksheet.Cell(row, 9).Value = item.InterviewPeople;
            }

            // 5. 自动调整列宽以适应内容
            worksheet.Columns().AdjustToContents();

            // 6. 将工作簿保存到内存流并转换为字节数组返回
            using var ms = new MemoryStream();
            workbook.SaveAs(ms);
            return ms.ToArray();
        }
    }
}
